#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time    : 2019/9/22 0022 21:05
# @Author  : GXl
# @File    : views.py
# @Software: win10 Tensorflow1.13.1 python3.7

import hashlib
import json,time,os
import qrcode
from flask import request,send_from_directory
from . import other
from utils.apiutils import *
from utils.dtutils import now2str,now2ymd
from app import db,auth,redis_client
from app.models import BookDetail,UserCollection,ShoppingCart,Address,UserOrder
from utils import logutils
from sqlalchemy.sql import func,desc


logger = logutils.getlogger(__file__)

"""
健康检查
"""
@other.route('/health', methods=['GET', 'POST'])
def health():
    logger.debug("****** 进入主目录 *****")
    return "OK"

"""
测试相关
"""
@other.route('/', methods=['GET', 'POST'])
@auth.login_required
def index():
    return "OK"

"""
测试相关
"""
@other.route("/test", methods=['GET', 'POST','DELETE','PUT'])
def test():
    return jsonData("test ok")

@other.route("/testerror")
def myfunc():
    1/0
    return "Hello World"

"""
书籍查询相关
"""

@other.route('/findallbooks', methods=['GET'])
@auth.login_required
def findallbooks():
    bookdetails = db.session.query(BookDetail).all()
    return jsonDataList(bookdetails)


# @other.route('/findbookbyid/<int:id>', methods=['GET', 'POST'])
# @auth.login_required
# def findbookby_id(id):
#     bookdetails = db.session.query(BookDetail).filter_by(id=id).all()
#     return jsonDataList(bookdetails)
#
# @other.route('/findbookbydoubanid/<int:doubanid>', methods=['GET', 'POST'])
# @auth.login_required
# def findbookby_doubanid(doubanid):
#     bookdetails = db.session.query(BookDetail).filter_by(douban_id=doubanid).all()
#     return jsonDataList(bookdetails)

@other.route('/findbooksbytag', methods=['GET', 'POST'])
@auth.login_required
def findbooksby_tag():
    logger.debug("******************findbooksby_tag*********************")
    tag=json.loads(request.data)['tag']
    if tag=='全部':
        bookdetails = db.session.query(BookDetail).all()
    else:
        bookdetails = db.session.query(BookDetail).filter(BookDetail.tags.like('%'+tag+'%')).all()
    return jsonDataList(bookdetails)

"""
收藏相关
"""
#查找用户收藏
@other.route('/findusercolbyuserid', methods=['GET', 'POST'])
@auth.login_required
def findusercolby_userid():
    logger.info("******************findusercolby_userid*********************")
    userid=json.loads(request.data)['userid']
    logger.info("userid={}".format(userid))
    usercols=db.session.query(UserCollection.bookid).filter(UserCollection.userid==userid).all()
    logger.info(usercols)
    bookcols=db.session.query(BookDetail).filter(BookDetail.id.in_(tuple([item[0] for item in usercols]))).all()
    logger.info(bookcols)
    return jsonDataList(bookcols)

#添加用户收藏
@other.route('/addbookcol', methods=['GET', 'POST','PUT'])
@auth.login_required
def addbookcol():
    logger.debug("******************addbookcol*********************")
    params=json.loads(request.data)
    userid=params['params']['userid']
    bookid=params['params']['bookid']
    logger.debug("params={}".format(params))
    res = db.session.execute(
        """
        select count(*) from usercollection where userid={} and bookid={}
    """.format(userid,bookid)).fetchall()
    if res:
        cnt=res[0][0]
        logger.debug("cnt={}".format(cnt))
        if cnt>0:
            return jsonData("该书已收藏！")
        else:
            db.session.execute(
                """
                insert into usercollection (userid,username,bookid,douban_id) select user.id as userid ,user.name as username,other.id as bookid,other.douban_id as douban_id  from user,bookdetail other where user.id={} and other.id={}
            """.format(userid, bookid))
            db.session.commit()
            return jsonData("收藏成功！")
    else:
        return jsonerror("内部错误")
    return jsonData("收藏成功！")

@other.route('/delbookcol', methods=['GET', 'POST','DELETE'])
@auth.login_required
def delbookcol():
    logger.debug("******************delbookcol*********************")
    params=json.loads(request.data)
    userid=params['params']['userid']
    bookid=params['params']['bookid']
    logger.info("params={}".format(params))
    res = db.session.execute(
        """
        select count(*) from usercollection where userid={} and bookid={}
    """.format(userid,bookid)).fetchall()
    if res:
        cnt=res[0][0]
        logger.debug("cnt={}".format(cnt))
        if cnt>0:
            db.session.execute(
                """
                delete from usercollection where userid={} and bookid={}
            """.format(userid, bookid))
            db.session.commit()
            return jsonData("删除成功！")
        else:
            return jsonData("未收藏该书！")
    else:
        return jsonerror("内部错误")
    return jsonData("删除成功！")

"""
购物车相关
"""

#查询购物车
@other.route('/findshoppingcartitemsbyuserid', methods=['GET', 'POST','DELETE'])
@auth.login_required
def findshoppingcaritemsby_userid():
    logger.info("******************findshoppingcaritemsby_userid*********************")
    logger.debug(request.data)
    params=json.loads(request.data)
    userid=params['userid']
    logger.debug("userid={}".format(userid))
    shoppingItems=db.session.query(ShoppingCart).filter_by(userid = userid).filter_by(status = 1).all()
    return jsonDataListWithSupplement(shoppingItems,count=len(shoppingItems))


#添加购物车
@other.route('/addshoppingcart', methods=['GET', 'POST','PUT'])
@auth.login_required
def addshoppingcart():
    logger.info("******************addshoppingcart*********************")
    params=json.loads(request.data)
    userid=params['params']['userid']
    bookid=params['params']['bookid']
    logger.info("params={}".format(params))
    res = db.session.execute(
        """
        select count(*) from shoppingcart where userid={} and bookid={} and status=1
    """.format(userid,bookid)).fetchall()
    if res:
        cnt=res[0][0]
        logger.debug("cnt={}".format(cnt))
        if cnt>0:
            db.session.execute(
                """
                update shoppingcart set num=num+1,createTime=UNIX_TIMESTAMP(NOW()) where userid={} and bookid={} and status=1
            """.format(userid, bookid))
            db.session.commit()
            count = db.session.query(func.count(ShoppingCart.id)).filter(ShoppingCart.userid == userid).filter(ShoppingCart.status == 1).scalar()
            return jsonMsgWithSupplement("已添加购物车！",count=count)
        else:
            db.session.execute(
                """
                insert into shoppingcart (userid,username,bookid,douban_id,bookname,authors,price,num,status,createTime) select user.id as userid ,user.name as username,other.id as bookid,other.douban_id as douban_id,other.name as bookname,other.authors as authors,other.price as price,1 as num,1 as status, UNIX_TIMESTAMP(NOW()) as createTime  from user,bookdetail other where user.id={} and other.id={}
            """.format(userid, bookid))
            db.session.commit()
            count = db.session.query(func.count(ShoppingCart.id)).filter(ShoppingCart.userid == userid).filter(ShoppingCart.status == 1).scalar()
            db.session.commit()
            return jsonMsgWithSupplement("添加购物车成功！",count=count)

    else:
        return jsonerror("内部错误")

#减少购物车中的数量
#删除购物车
@other.route('/decreaseshoppingcart', methods=['GET', 'POST','DELETE'])
@auth.login_required
def decreaseshoppingcart():
    logger.info("******************decreaseshoppingcart*********************")
    params=json.loads(request.data)
    userid=params['params']['userid']
    bookid=params['params']['bookid']
    logger.info("params={}".format(params))
    res = db.session.execute(
        """
        select num from shoppingcart where userid={} and bookid={} and status=1
    """.format(userid,bookid)).fetchall()
    if res:
        num=res[0][0]
        logger.debug("num={}".format(num))
        if num>1:
            db.session.execute(
                """
                update shoppingcart set num=num-1 where userid={} and bookid={} and status=1
            """.format(userid, bookid))
            db.session.commit()
            count = db.session.query(func.count(ShoppingCart.id)).filter(ShoppingCart.userid == userid).filter(
                ShoppingCart.status == 1).scalar()
            # db.session.commit()
            return jsonMsgWithSupplement("删除成功！", count=count)
        else:
            return jsonMsg("不能再减少了！")
    else:
        return jsonerror("内部错误")

#删除购物车
@other.route('/delshoppingcart', methods=['GET', 'POST','DELETE'])
@auth.login_required
def delshoppingcart():
    logger.info("******************delshoppingcart*********************")
    params=json.loads(request.data)
    userid=params['params']['userid']
    bookid=params['params']['bookid']
    logger.info("params={}".format(params))
    res = db.session.execute(
        """
        select count(*) from shoppingcart where userid={} and bookid={} and status=1
    """.format(userid,bookid)).fetchall()
    if res:
        cnt=res[0][0]
        logger.debug("cnt={}".format(cnt))
        if cnt>0:
            db.session.execute(
                """
                update  shoppingcart set status=-1 where userid={} and bookid={} and status=1
            """.format(userid, bookid))
            db.session.commit()
            count = db.session.query(func.count(ShoppingCart.id)).filter(ShoppingCart.userid == userid).filter(
                ShoppingCart.status == 1).scalar()
            # db.session.commit()
            return jsonMsgWithSupplement("删除成功！", count=count)
        else:
            return jsonData("购物车中没有该书！")
    else:
        return jsonerror("内部错误")
    return jsonData("删除成功！")


"""
支付相关
"""

@other.route('/finduseraddresses', methods=['GET', 'POST'])
# @auth.login_required
def findUserAddresses():
    logger.debug("******************findUserAddresses*********************")
    logger.debug(request.data)
    params=json.loads(request.data)
    userid=params['userid']
    addresses = db.session.query(Address).filter_by(userid = userid).all()
    # db.session.commit()
    print(addresses)
    tmplst=[]
    for item in addresses:
        tmplst.append("{} {} {}".format(item.name,item.telephone,item.address) )
    return jsonDataList(tmplst)

#创建支付订单
@other.route('/createpayment', methods=['GET', 'POST'])
@auth.login_required
def createPayment():
    logger.debug("******************createPayment*********************")
    logger.debug(request.data)
    params=json.loads(request.data)
    #拆解数据结构
    tmpdata={key:val for key,val in params['params'].items()}
    logger.debug("params={}".format(params))
    userid=tmpdata['userid']
    data_key = "order/%s" % userid
    data = redis_client.get(data_key)
    if data:
        return jsonerror("创建订单失败，您有未支付的订单，请先支付或取消订单！")
    data = json.dumps(tmpdata,ensure_ascii=False)
    #redis事务提交
    expires = int(time.time()) + 30*60
    # expires = int(time.time()) + 30
    p = redis_client.pipeline()
    p.set(data_key, data)
    p.expireat(data_key, expires)
    p.execute()
    data=redis_client.get(data_key)
    if data:
        data=json.loads(data,encoding='utf-8')
        bookids=','.join([str(item['bookid']) for item in data['order']])
        print(bookids)
        sql='update  shoppingcart set status=-1 where userid={} and bookid in ({}) and status=1'.format(userid, bookids)
        db.session.execute(sql)
        db.session.commit()
        count = db.session.query(func.count(ShoppingCart.id)).filter(ShoppingCart.userid == userid).filter(
            ShoppingCart.status == 1).scalar()
        # db.session.commit()
    return jsonMsgWithSupplement("生成支付订单成功！",count=count)

@other.route('/findpaymentbyuserid', methods=['GET', 'POST'])
@auth.login_required
def findPaymentByUserId():
    logger.debug("******************findPaymentByUserId*********************")
    logger.debug(request.data)
    params=json.loads(request.data)
    userid=params['userid']
    data_key = "order/%s" % userid
    rawdata=redis_client.get(data_key)
    if rawdata:
        data = json.loads(rawdata, encoding = 'utf-8')
        data['ttl'] = redis_client.ttl(data_key)
        return jsonData(data)
    else:
        return jsonData([],responseText='没有未支付订单！')

#生成二维码
@other.route('/buildqrcodebyuserid', methods=['GET', 'POST'])
@auth.login_required
def buildQrcodeByUSerId():
    logger.debug("******************buildQrcodeByUSerId*********************")
    logger.debug(request.data)
    params=json.loads(request.data)
    userid=params['userid']
    img = qrcode.make('{} 我假装这是一个付款二维码'.format(now2str()))
    dirname=os.path.join(os.getcwd(), 'download')
    imgname='qrcode_'+str(userid)+'_'+str(int(time.time()))+'.jpg'
    qrcodepath=os.path.join(dirname,imgname)
    with open(qrcodepath,'wb') as file:
        img.save(file)
    return jsonMsg(imgname)

@other.route('/getqrcodebyimgname/<imgname>', methods=['GET', 'POST'])
# @auth.login_required
def getQrcodeByUSerId(imgname):
    logger.debug("******************findOrderByUserId*********************")
    dirname=os.path.join(os.getcwd(), 'download')
    return send_from_directory(dirname,imgname,as_attachment=True)

#订单相关

@other.route('/findordersbyuserid', methods=['GET', 'POST'])
@auth.login_required
def findOrdersByUserid():
    logger.debug("******************findOrdersByUserid*********************")
    logger.debug(request.data)
    params=json.loads(request.data)
    userid = params['userid']
    datas = db.session.query(UserOrder).filter_by(userid=userid).order_by(desc(UserOrder.createtime)).all()
    # db.session.commit()
    lst = []
    for item in datas:
        assert isinstance(item, UserOrder)
        lst.append({'orderid':item.orderid,'userid': item.userid, 'content': item.content, 'createtime': item.createtime})
    return jsonData(lst)


@other.route('/createorder', methods=['GET', 'POST'])
@auth.login_required
def createOrder():
    logger.debug("******************createOrder*********************")
    logger.debug(request.data)
    params=json.loads(request.data)
    userid = params['userid']
    data_key = "order/%s" % userid
    rawdata = redis_client.get(data_key)
    if rawdata:
        datastr=str(rawdata,encoding='utf-8')
        createtime=int(time.time())
        m=hashlib.md5()
        m.update(json.dumps({'datastr': datastr, 'createtime': str(createtime)}).encode('utf-8'))
        md5str=m.hexdigest()
        orderid='{}-{}'.format(now2ymd(),md5str.upper()[0:8])
        sql="insert into userorder (orderid,userid,content,createtime)values ('{}',{},'{}',{})".format(orderid,userid,datastr,createtime);
        db.session.execute(sql)
        db.session.commit()
        #删除redis中的数据
        redis_client.delete(data_key)
        return jsonData("创建订单成功!")
    else:
        return jsonData([], responseText='未找到有效的待支付订单！')